package com.fastmms.generate;

import com.fastmms.config.FastMmsConfig;
import com.fastmms.utils.ByteUtil;

import java.io.File;
import java.io.RandomAccessFile;
import java.util.LinkedList;
import java.util.List;

public class GenerateMessageBody {

    private List<GenerateIndexData> indexDataList;
    private String filePath;
    private RandomAccessFile file;
    private byte[] tempData = null;
    private int writePoint = 0;
    private long fileNo;
    private long msgStartNo;
    private long msgCount;
    private boolean isInit = false;

    public void start(String filePath,long fileNo,long msgStartNo) throws Exception {
        File file = new File(filePath);
        if (!file.exists()) {
            file.createNewFile();
        }
        this.filePath = filePath;
        this.file = new RandomAccessFile(filePath, "rw");
        this.indexDataList = new LinkedList<>();
        this.tempData = new byte[FastMmsConfig.GENERATE_BLOCK_SIZE];
        this.fileNo = fileNo;
        this.msgStartNo = msgStartNo;
        isInit = true;
    }


    private GenerateIndexData createIndexData(long index){
        GenerateIndexData data = new GenerateIndexData();
        data.setBlockIndex(index);
        data.setMsgStartNo(msgStartNo);
        data.setMsgCount(msgCount);
        data.setFileNo(fileNo);
        msgStartNo += msgCount;
        msgCount = 0;
        return data;
    }


    public void add(byte[] keyData, byte[] valueData) throws Exception {
        if (!isInit) {
            throw new Exception("没有执行start！");
        }

        // 如果消息数据大于消息块长度，需要保存之前的数据并且重新生成消息块大小
        if(keyData.length + valueData.length + 8 > tempData.length){
            if(writePoint > 0){
                file.write(tempData,0,writePoint);
                indexDataList.add( createIndexData(file.length()) );
            }
            tempData = new byte[keyData.length + valueData.length + 8 ];
            writePoint = 0;
        }

        if( keyData.length + valueData.length + 8 > tempData.length - writePoint){
            file.write(tempData,0,writePoint);
            indexDataList.add( createIndexData(file.length()) );
            writePoint = 0;
        }

        long keySize = keyData.length;
        byte[] keyByte = ByteUtil.toByteArray((int) keySize);
        System.arraycopy(keyByte,0,tempData,writePoint,keyByte.length);
        writePoint += keyByte.length;
        if (keySize > 0) {
            System.arraycopy(keyData,0,tempData,writePoint,keyData.length);
            writePoint += keyData.length;
        }

        long valueSize = valueData.length;
        byte[] valueByte = ByteUtil.toByteArray((int) valueSize);
        System.arraycopy(valueByte,0,tempData,writePoint,valueByte.length);
        writePoint += valueByte.length;
        if (keySize > 0) {
            System.arraycopy(valueData,0,tempData,writePoint,valueData.length);
            writePoint += valueData.length;
        }
        msgCount++;
    }

    public long end() throws Exception {
        if (!isInit) {
            return this.msgStartNo;
        }
        // 收尾最后的消息成一个消息块
        if ( writePoint > 0) {
            file.write(tempData,0,writePoint);
            indexDataList.add( createIndexData(file.length()) );
        }
        writePoint = 0;
        tempData = null;
        file.close();
        file = null;
        isInit = false;
        return this.msgStartNo;
    }

    public List<GenerateIndexData> getIndexDataList() {
        return indexDataList;
    }

    public String getFilePath() {
        return filePath;
    }
}
